#include "video.h"
#include "header.h"
#include "log.h"
#include "utils.h"
#include <fstream>

using std::cout;
using std::endl;
using std::ofstream;

void ClearTempFile(const string filename)
{
    ofstream file(filename);

    if ((file.rdstate() & ofstream::failbit) == 0) {
        file.flush();
        ALOGD("清空文件%s\n", filename.c_str());
        file.close();
        return;
    }
    file.close();
    ALOGE("文件%s打开失败\n", filename.c_str());
}

void AppendTempFile(const string filename, const char* data)
{
    static int times = 0;
    string inp(data);
    string out;
    size_t len = Base64::DecodedLength(inp);
    if (inp != "") {
        Base64::Decode(inp, &out);
    }
    ofstream file(filename, ofstream::ate | ofstream::app | ofstream::binary);

    if (file.is_open()) {
        Base64::Decode(data, inp.size(), &out[0], len);
        cout << "file size: " << inp.size() << endl;
        file << out;
        ALOGD("写入临时文件%d次\n", ++times);
        return;
    }
    file.close();
    ALOGE("文件%s打开失败\n", filename.c_str());
}
Video::Video(std::vector<char>& vcd, int bounds)
    : mBatch(0)
    , mNext(0)
{
    std::string jData(vcd.data(), vcd.data() + bounds);

    json_error_t err;
    ALOGD("协议体大小: %ld", jData.size());
    mBody = json_loads(jData.data(), 0, &err);

    if (!mBody) {
        ALOGE("json_loads fail: %s\n", err.text);
    }
}

Video::~Video()
{
    if (mBody) {
        json_decref(mBody);
        mBody = nullptr;
    }
}

Response Video::GetHandleResult()
{
    Response ret;
    json_error_t jerr;
    int cmd;
    int batch = 0;
    size_t size = 0;
    const char* err;
    const char* vname;
    const char* data;

    if (!json_unpack_ex(mBody, &jerr, JSON_STRICT, "{s:i, s?i, s?i, s?i, s?s, s?s, s?i, s?s}",
            "command", &cmd,
            "batch", &mBatch,
            "next_batch", &mNext,
            "vid", &mVid,
            "err", &err,
            "vname", &vname,
            "size", &size,
            "data", &data)) {
        switch ((Command)cmd) {
        case Command::LS: {
            ret.name = "LS";
            ret.res = data;
            break;
        }
        case Command::INFO: {
            float MB = (float)size / (1024 * 1024);
            ret.name = "INFO";
            ret.res += "视频ID: " + std::to_string(mVid) + "\n";
            ret.res += "视频名称: " + string(vname) + "\n";
            ret.res += "视频大小: " + std::to_string(MB) + "MB\n";
            break;
        }
        case Command::PLAY: {
            // 清空临时文件
            ClearTempFile("vvv.mp4");
            break;
        }
        case Command::PLAY_START: {
            // 写入临时文件
            AppendTempFile("vvv.mp4", data);
        }
        }
    } else {
        ALOGE("解析json错误: %s", jerr.text);
    }
    return ret;
}

void Video::PostPlay()
{
    if (mBatch && mNext <= mBatch) {
        // 存在该video，且还未传输完成
        std::string cmd = "PLAY_START";
        json_t* body = NULL;
        body = json_pack("{s:i, s:i, s:i, s:i}",
            "command", Command::PLAY_START,
            "vid", mVid,
            "next_batch", ++mNext,
            "batch", mBatch);
        int st;
        if (body) {
            ClientProxy::getInstance().send(cmd, body, st);
        }
        if (!st) {
            // 发送失败
            ALOGD("vid = %d, next_batch = %d\n", mVid, mNext);
        }
    } else {
        ALOGD("传输完成：共传输%d次\n", mBatch);
    }
}
